package com.cowealth.platform.common.web.aspect;

import com.cowealth.platform.common.base.constant.GlobalReturnCodeConstants;
import com.cowealth.platform.common.base.util.EnDecoderUtils;
import com.cowealth.platform.common.base.util.GsonUtils;
import com.cowealth.platform.common.base.vo.result.CommonResult;
import com.cowealth.platform.common.web.annotation.ParamFilter;
import com.google.gson.Gson;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Pointcut;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

import javax.servlet.http.HttpServletRequest;
import java.util.HashMap;

/**
 * 请求参数过滤注解切面处理逻辑
 * @author      : skycdm
 * @date        : 2020/6/30 14:56
 * @version     : 1.0.0
 */
@Aspect
@Component
public class ParamsFilterAspect {

    @Pointcut("@annotation(com.cowealth.platform.common.base.annotation.ParamFilter)")
    public void pointcut() {
    }

    @Around("@annotation(paramFilter)")
    public Object filterParam(ProceedingJoinPoint joinPoint, ParamFilter paramFilter) {
        HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest();
        //处理判断请求体
        if (paramFilter.body()) {
            Object[] args = joinPoint.getArgs();
            if (args == null || args.length == 0) {
                return CommonResult.error(GlobalReturnCodeConstants.BAD_REQUEST.getCode(),
                        GlobalReturnCodeConstants.BAD_REQUEST.getMessage() + ": con not found request body");
            }
            Object body = args[paramFilter.bodyArgIdx()];
            String requestBody;
            if (body instanceof String) {
                requestBody = body.toString();
            } else {
                requestBody = GsonUtils.toJson(body);
            }
            if (StringUtils.isEmpty(requestBody)) {
                return CommonResult.error(GlobalReturnCodeConstants.BAD_REQUEST.getCode(),
                        GlobalReturnCodeConstants.BAD_REQUEST.getMessage() + ": con not found request body");
            }
            requestBody = EnDecoderUtils.decoder(requestBody);
            Gson gson = new Gson();
            HashMap map = gson.fromJson(requestBody, HashMap.class);
            for (String name : paramFilter.notNull()) {
                Object obj = map.get(name);
                if (StringUtils.isEmpty(obj)) {
                    return CommonResult.error(GlobalReturnCodeConstants.BAD_REQUEST.getCode(),
                            GlobalReturnCodeConstants.BAD_REQUEST.getMessage() + ": " + name);
                }
            }
        } else if (paramFilter.header()) {
            for (String name : paramFilter.notNull()) {
                Object obj = request.getHeader(name);
                if (StringUtils.isEmpty(obj)) {
                    return CommonResult.error(GlobalReturnCodeConstants.BAD_REQUEST.getCode(),
                            GlobalReturnCodeConstants.BAD_REQUEST.getMessage() + ": " + name);
                }
            }
        } else {
            for (String name : paramFilter.notNull()) {
                Object obj = request.getParameter(name);
                if (StringUtils.isEmpty(obj)) {
                    return CommonResult.error(GlobalReturnCodeConstants.BAD_REQUEST.getCode(),
                            GlobalReturnCodeConstants.BAD_REQUEST.getMessage() + ": " + name);
                }
            }
        }

        Object result = null;
        try {
            result = joinPoint.proceed();
        } catch (Throwable throwable) {
            throwable.printStackTrace();
        }
        return result;
    }
}
